package com.car.rental.order.service.impl;

import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.car.rental.common.core.exception.BusinessException;
import com.car.rental.common.core.response.ResponseResult;
import com.car.rental.order.dto.PaymentDTO;
import com.car.rental.order.entity.PaymentRecord;
import com.car.rental.order.entity.RentalOrder;
import com.car.rental.order.enums.OrderStatus;
import com.car.rental.order.enums.PaymentStatus;
import com.car.rental.order.mapper.PaymentRecordMapper;
import com.car.rental.order.service.PaymentService;
import com.car.rental.order.service.MessageService;
import lombok.RequiredArgsConstructor;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.amqp.rabbit.core.RabbitTemplate;

import java.util.UUID;

@Service
@RequiredArgsConstructor
public class PaymentServiceImpl extends ServiceImpl<PaymentRecordMapper, PaymentRecord> implements PaymentService {

    private final MessageService messageService;
    private final OrderServiceImpl orderService;

    @Override
    @Transactional(rollbackFor = Exception.class)
    public ResponseResult<String> createPayment(Long userId, PaymentDTO paymentDTO) {
        // 1. 查询订单
        RentalOrder order = orderService.getByOrderNo(userId, paymentDTO.getOrderNo());
        
        // 2. 检查订单状态
        if (order.getStatus() != OrderStatus.PENDING_PAYMENT.getCode()) {
            throw new BusinessException("订单状态不正确");
        }
        
        // 3. 生成支付流水号
        String paymentNo = UUID.randomUUID().toString().replace("-", "");
        
        // 4. 创建支付记录
        PaymentRecord payment = new PaymentRecord();
        payment.setOrderId(order.getId());
        payment.setOrderNo(order.getOrderNo());
        payment.setPaymentNo(paymentNo);
        payment.setAmount(paymentDTO.getAmount());
        payment.setStatus(PaymentStatus.PENDING.getCode());
        payment.setPaymentMethod(paymentDTO.getPaymentMethod());
        
        // 创建支付记录并返回
        save(payment);
        // 发送待支付状态消息
        messageService.sendPaymentStatusMessage(paymentNo, order.getVehicleId(), PaymentStatus.PENDING.getCode());
        return ResponseResult.success(paymentNo);
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public ResponseResult<Void> paymentSuccess(String paymentNo) {
        // 1. 查询支付记录
        PaymentRecord payment = getByPaymentNo(paymentNo);
        
        // 2. 更新支付状态
        payment.setStatus(PaymentStatus.SUCCESS.getCode());
        updateById(payment);
        
        // 3. 更新订单状态
        RentalOrder order = orderService.getById(payment.getOrderId());
        order.setStatus(OrderStatus.PAID.getCode());
        orderService.updateById(order);
        
        // 4. 发送支付成功消息
        messageService.sendPaymentStatusMessage(paymentNo, order.getVehicleId(), PaymentStatus.SUCCESS.getCode());
        
        return ResponseResult.success();
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public ResponseResult<Void> paymentFailed(String paymentNo, String reason) {
        // 1. 查询支付记录
        PaymentRecord payment = getByPaymentNo(paymentNo);
        
        // 2. 更新支付状态
        payment.setStatus(PaymentStatus.FAILED.getCode());
        updateById(payment);
        
        // 3. 获取订单信息
        RentalOrder order = orderService.getById(payment.getOrderId());
        
        // 4. 发送支付失败消息
        messageService.sendPaymentStatusMessage(paymentNo, order.getVehicleId(), PaymentStatus.FAILED.getCode());
        
        return ResponseResult.success();
    }

    @Override
    public ResponseResult<Integer> getPaymentStatus(String orderNo) {
        PaymentRecord payment = getOne(new LambdaQueryWrapper<PaymentRecord>()
                .eq(PaymentRecord::getOrderId, orderNo)
                .orderByDesc(PaymentRecord::getCreateTime)
                .last("LIMIT 1"));
                
        return ResponseResult.success(payment != null ? payment.getStatus() : null);
    }

    @Override
    public PaymentRecord getByPaymentNo(String paymentNo) {
        // 最多重试3次，每次间隔1秒
        int maxRetries = 3;
        int retryCount = 0;
        PaymentRecord payment = null;
        
        while (retryCount < maxRetries) {
            payment = getOne(new LambdaQueryWrapper<PaymentRecord>()
                    .eq(PaymentRecord::getPaymentNo, paymentNo));
                    
            if (payment != null) {
                return payment;
            }
            
            retryCount++;
            if (retryCount < maxRetries) {
                try {
                    Thread.sleep(1000); // 等待1秒后重试
                } catch (InterruptedException e) {
                    Thread.currentThread().interrupt();
                    break;
                }
            }
        }
        
        if (payment == null) {
            throw new BusinessException("支付记录不存在");
        }
        
        return payment;
    }

    @Override
    public boolean updateById(PaymentRecord payment) {
        return super.updateById(payment);
    }
} 